package com.ruoyi.ring.service.impl;

import cn.hutool.core.convert.Convert;
import com.google.gson.Gson;
import com.ruoyi.common.core.domain.entity.SysUser;
import com.ruoyi.common.enums.PlanAssortEnums;
import com.ruoyi.common.enums.PlanStatusEnums;
import com.ruoyi.common.exception.ServiceException;
import com.ruoyi.common.utils.DateUtils;
import com.ruoyi.common.utils.SecurityUtils;
import com.ruoyi.common.utils.bean.Builder;
import com.ruoyi.ora.constant.BizConstants;
import com.ruoyi.ring.domain.HealthQuestionAnswer;
import com.ruoyi.ring.domain.RingHealthPlan;
import com.ruoyi.ring.domain.dto.UserHealthQuestionDTO;
import com.ruoyi.ring.domain.vo.HealthQuestionAnswerVO;
import com.ruoyi.ring.domain.vo.UserHealthQuestionVO;
import com.ruoyi.ring.factory.AiFactory;
import com.ruoyi.ring.mapper.HealthQuestionAnswerMapper;
import com.ruoyi.ring.mapper.RingHealthPlanMapper;
import com.ruoyi.ring.service.IHealthQuestionAnswerService;
import com.ruoyi.system.mapper.SysUserMapper;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.annotation.Resource;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.Map;

/**
 * 问卷答案Service业务层处理
 * 
 * @author liuwp
 * @date 2025-07-29
 */
@Slf4j
@Service
public class HealthQuestionAnswerServiceImpl implements IHealthQuestionAnswerService 
{
    @Resource
    private HealthQuestionAnswerMapper healthQuestionAnswerMapper;
    @Resource
    private SysUserMapper sysUserMapper;
    @Resource
    private RingHealthPlanMapper ringHealthPlanMapper;

    /**
     * 查询问卷答案
     * 
     * @param id 问卷答案主键
     * @return 问卷答案
     */
    @Override
    public HealthQuestionAnswer selectHealthQuestionAnswerById(Long id)
    {
        return healthQuestionAnswerMapper.selectHealthQuestionAnswerById(id);
    }

    /**
     * 查询问卷答案列表
     * 
     * @param healthQuestionAnswer 问卷答案
     * @return 问卷答案
     */
    @Override
    public List<HealthQuestionAnswer> selectHealthQuestionAnswerList(HealthQuestionAnswer healthQuestionAnswer)
    {
        return healthQuestionAnswerMapper.selectHealthQuestionAnswerList(healthQuestionAnswer);
    }

    /**
     * 根据业务主键查询一条记录：问卷答案
     *
     * @param healthQuestionAnswer 问卷答案
     * @return 问卷答案
     */
    @Override
    public HealthQuestionAnswer selectOneHealthQuestionAnswer(HealthQuestionAnswer healthQuestionAnswer)
    {
        return healthQuestionAnswerMapper.selectOneHealthQuestionAnswer(healthQuestionAnswer);
    }

    /**
     * 新增问卷答案
     * 
     * @param healthQuestionAnswer 问卷答案
     * @return 结果
     */
    @Override
    public int insertHealthQuestionAnswer(HealthQuestionAnswer healthQuestionAnswer)
    {
        healthQuestionAnswer.setCreateTime(DateUtils.getNowDate());
        return healthQuestionAnswerMapper.insertHealthQuestionAnswer(healthQuestionAnswer);
    }

    /**
     * 修改问卷答案
     * 
     * @param healthQuestionAnswer 问卷答案
     * @return 结果
     */
    @Override
    public int updateHealthQuestionAnswer(HealthQuestionAnswer healthQuestionAnswer)
    {
        healthQuestionAnswer.setUpdateTime(DateUtils.getNowDate());
        return healthQuestionAnswerMapper.updateHealthQuestionAnswer(healthQuestionAnswer);
    }

    @Override
    public int updateHealthQuestionAnswerCondition(HealthQuestionAnswer healthQuestionAnswer, HealthQuestionAnswer healthQuestionAnswerCondition)
    {
                healthQuestionAnswer.setUpdateTime(DateUtils.getNowDate());
        return healthQuestionAnswerMapper.updateHealthQuestionAnswerCondition(healthQuestionAnswer, healthQuestionAnswerCondition);
    }

    /**
     * 批量删除问卷答案
     * 
     * @param ids 需要删除的问卷答案主键
     * @return 结果
     */
    @Override
    public int deleteHealthQuestionAnswerByIds(Long[] ids)
    {
        return healthQuestionAnswerMapper.deleteHealthQuestionAnswerByIds(ids);
    }

    /**
     * 删除问卷答案信息
     * 
     * @param id 问卷答案主键
     * @return 结果
     */
    @Override
    public int deleteHealthQuestionAnswerById(Long id)
    {
        return healthQuestionAnswerMapper.deleteHealthQuestionAnswerById(id);
    }

    /**
     * 条件删除问卷答案
     *
     * @param healthQuestionAnswer 问卷答案
     * @return 结果
     */
    @Override
    public int deleteHealthQuestionAnswerByCondition(HealthQuestionAnswer healthQuestionAnswer)
    {
        return healthQuestionAnswerMapper.deleteHealthQuestionAnswerByCondition(healthQuestionAnswer);
    }

    @Transactional(rollbackFor = Exception.class)
    @Override
    public Long addHealthQuestionAnswer(UserHealthQuestionDTO userHealthQuestionDTO) {
        try {
            long userId = SecurityUtils.getUserId();
            RingHealthPlan ringHealthPlan = new RingHealthPlan();
            SysUser sysUser = Convert.convert(SysUser.class,userHealthQuestionDTO);
            sysUser.setUserId(userId);
            if(userHealthQuestionDTO.getExerciseList().size() > 0){
                //运动
                List<HealthQuestionAnswer> exerciseAnswers = Convert.toList(HealthQuestionAnswer.class,userHealthQuestionDTO.getExerciseList());
                String questionAnswer = exercise(exerciseAnswers, ringHealthPlan, sysUser);
                //睡眠
                List<HealthQuestionAnswer> sleepAnswers = Convert.toList(HealthQuestionAnswer.class,userHealthQuestionDTO.getSleepList());
                sleep(sleepAnswers, ringHealthPlan);
                //饮食
                List<HealthQuestionAnswer> dietAnswers = Convert.toList(HealthQuestionAnswer.class,userHealthQuestionDTO.getDietList());
                diet(dietAnswers, ringHealthPlan,sysUser, questionAnswer);
                //情绪
                List<HealthQuestionAnswer> emotionAnswers = Convert.toList(HealthQuestionAnswer.class,userHealthQuestionDTO.getEmotionList());
                emotion(emotionAnswers, ringHealthPlan);
                //周期
                List<HealthQuestionAnswer> periodAnswers = Convert.toList(HealthQuestionAnswer.class,userHealthQuestionDTO.getPeriodList());
                period(emotionAnswers, ringHealthPlan);
                sysUserMapper.updateUser(sysUser);

                List<HealthQuestionAnswer> answers = new ArrayList<>();
                answers.addAll(exerciseAnswers);
                answers.addAll(sleepAnswers);
                answers.addAll(dietAnswers);
                answers.addAll(emotionAnswers);
                answers.addAll(periodAnswers);
                if(answers.size() > 0){
                    answers.forEach(answer ->{
                        answer.setUserId(userId);
                        answer.setCreateTime(new Date());
                        healthQuestionAnswerMapper.insertHealthQuestionAnswer(answer);
                    });
                }
            }else {
                ringHealthPlan.setPlanCycle(15);
                ringHealthPlan.setRestingHeartRate("60-100");
                ringHealthPlan.setBloodOxygenSaturation("95-100");
                ringHealthPlan.setHeartRateVariability("个人基线未形成");
                ringHealthPlan.setSleepQuality("良");
                ringHealthPlan.setEmotionManagement("25-60");
                ringHealthPlan.setStepCount(5000);
                ringHealthPlan.setExerciseDuration(30);
                ringHealthPlan.setExerciseCalorie(300);
                ringHealthPlan.setCalorie(Convert.toStr(150));
                String aiContent = "生成三个当日推荐事件返回XX（大于1000毫升）、XX（大于X分钟）、XX（大于X分钟），按照举例返回不超过8个字,例如：{\"shijian1\":\"xxx\",\"shijian2\":\"xxx\",\"shijian3\":\"xxx\"}，不要其他任何内容";
                String jsonStr = AiFactory.build(BizConstants.AI_PLATFORM.getValue()).chatCompletions(aiContent);
                Gson gson = new Gson();
                Map<String, Object> resultMap = gson.fromJson(jsonStr, Map.class);
                ringHealthPlan.setCheckInEvent(resultMap.get("shijian1")+","+ resultMap.get("shijian2")+","+ resultMap.get("shijian3"));
            }

            ringHealthPlan.setDeviceSn(userHealthQuestionDTO.getDeviceSn());
            ringHealthPlan.setPlanStatus(PlanStatusEnums.GENERATED.getCode());
            ringHealthPlan.setPlanName("健康问卷计划");
            ringHealthPlan.setPlanAssort(PlanAssortEnums.QUESTIONNAIRE.getCode());
            ringHealthPlan.setPlanStatus(PlanStatusEnums.GENERATED.getCode());
            ringHealthPlan.setUserId(userId);
            ringHealthPlan.setCreateTime(new Date());
            int result = ringHealthPlanMapper.insertRingHealthPlan(ringHealthPlan);
            return ringHealthPlan.getId();
        }catch (Exception e){
            log.error(e.getMessage());
            throw new ServiceException("健康问卷提交失败");
        }
    }

    public String exercise(List<HealthQuestionAnswer> exerciseAnswers, RingHealthPlan ringHealthPlan, SysUser sysUser){
        String answer1 = "";
        String answer2 = "";
        for (int i = 0; i < exerciseAnswers.size(); i++){
            HealthQuestionAnswer answer = exerciseAnswers.get(i);
            if(i == 0){
                answer1 = answer.getQuestionAnswer();
            }else {
                answer2 = answer.getQuestionAnswer();
            }
        }
        int s = 0; //步数
        double w = sysUser.getWeight(); //体重
        int h = sysUser.getHeight(); //身高
        double sl = Convert.toDouble(h)*0.415;// 步幅
        if("5000步以下".equals(answer2)){
            s = 5000;
        }
        if("5000-8000步".equals(answer2)){
            s = 9000;
        }
        if("8000-10000步".equals(answer2)){
            s = 12000;
        }
        if("10000步以上".equals(answer2)){
            s = 15000;
        }
        sysUser.setStepLength(sl);
        ringHealthPlan.setStepCount(s);
        ringHealthPlan.setExerciseCalorie(Convert.toInt(s*sl*w*0.0007));
        ringHealthPlan.setExerciseDuration(s/80);
        return answer1;
    }
    public void sleep(List<HealthQuestionAnswer> sleepAnswers, RingHealthPlan ringHealthPlan){
        int answer1 = 0;
        for (int i = 0; i < sleepAnswers.size(); i++){
            HealthQuestionAnswer answer = sleepAnswers.get(i);
            if(i == 0){
                if("少于6小时".equals(answer.getQuestionAnswer())){
                    answer1 = 5;
                }
                if("6-10小时".equals(answer.getQuestionAnswer())){
                    answer1 = 8;
                }
                if("超过10小时".equals(answer.getQuestionAnswer())){
                    answer1 = 11;
                }
            }else {
                break;
            }
        }
        String sleepQuality = "";//睡眠质量
        if(answer1 >= 6 &&  answer1 <= 10){
            sleepQuality = "优秀";
        }
        if(answer1 < 6 || answer1 > 10){
            sleepQuality = "良";
        }
        ringHealthPlan.setSleepQuality(sleepQuality);
    }
    public void diet(List<HealthQuestionAnswer> dietAnswers, RingHealthPlan ringHealthPlan, SysUser sysUser, String questionAnswer){
        double bmr = 0.0;
        //0=男,1=女
        String sex = sysUser.getSex();
        int age = DateUtils.calculateAge(sysUser.getBirthday());
        double w = sysUser.getWeight(); //体重
        int h = sysUser.getHeight(); //身高
        if("0".equals(sex)){//男
            bmr = 88.362+(13.397*w)+(4.799*h)-(5.677*age);
        }else {
            bmr = 447.593+(9.247*w)+(3.098*h)-(4.33*age);
        }
        String answer = questionAnswer.substring(0, questionAnswer.indexOf("("));
        double tdee = 0.0;
        if("几乎不运动".equals(answer)){
            tdee = bmr*1.2;
        }
        if("偶尔运动".equals(answer)){
            tdee = bmr*1.375;
        }
        if("经常运动".equals(answer)){
            tdee = bmr*1.55;
        }
        if("规律运动".equals(answer)){
            tdee = bmr*1.725;
        }
        String answer3 = "";
        for (int i = 0; i < dietAnswers.size(); i++){
            HealthQuestionAnswer s = dietAnswers.get(i);
            if(i == 2){
                answer3 = s.getQuestionAnswer();
            }
        }
        String calorie = "";
        if("减重".equals(answer3)){
            calorie = Convert.toStr(tdee - 500);
        }else if("维持当前体重".equals(answer3)){
            calorie = Convert.toStr(tdee);
        }else {
            calorie = Convert.toStr(tdee + 300);
        }
        ringHealthPlan.setCalorie(calorie);
    }
    public void emotion(List<HealthQuestionAnswer> emotionAnswers, RingHealthPlan ringHealthPlan){
        String answer1 = "";
        for (int i = 0; i < emotionAnswers.size(); i++){
            HealthQuestionAnswer answer = emotionAnswers.get(i);
            if(i == 0){
                answer1 = answer.getQuestionAnswer();
            }
        }
        String emotionManagement = "";
        if("几乎一直".equals(answer1)){
            emotionManagement = "50-79";
        }else if("经常".equals(answer1)){
            emotionManagement = "30-49";
        }else {
            emotionManagement = "0-29";
        }
        ringHealthPlan.setEmotionManagement(emotionManagement);
    }
    public void period(List<HealthQuestionAnswer> periodAnswers, RingHealthPlan ringHealthPlan){
        String answer1 = "";
        String answer2 = "";
        for (int i = 0; i < periodAnswers.size(); i++){
            HealthQuestionAnswer answer = periodAnswers.get(i);
            if(i == 0){
                answer1 = answer.getQuestionAnswer();
            }else {
                answer2 = answer.getQuestionAnswer();
            }
        }
        String aiContent = answer1+", 请给以上描述生成三个当日推荐事件返回XX（大于1000毫升）、XX（大于X分钟）、XX（大于X分钟），按照举例返回不超过8个字,例如：{\"shijian1\":\"xxx\",\"shijian2\":\"xxx\",\"shijian3\":\"xxx\"}，不要其他任何内容";
        String jsonStr = AiFactory.build(BizConstants.AI_PLATFORM.getValue()).chatCompletions(aiContent);
        Gson gson = new Gson();
        Map<String, Object> resultMap = gson.fromJson(jsonStr, Map.class);
        ringHealthPlan.setCheckInEvent(resultMap.get("shijian1")+","+ resultMap.get("shijian2")+","+ resultMap.get("shijian3"));
        ringHealthPlan.setPlanCycle(Convert.toInt(answer2.replace("天","")));
    }

    @Transactional(rollbackFor = Exception.class)
    @Override
    public int updHealthQuestionAnswer(UserHealthQuestionDTO userHealthQuestionDTO) {
        try {
            long userId = SecurityUtils.getUserId();
            RingHealthPlan ringHealthPlan = new RingHealthPlan();
            SysUser sysUser = Convert.convert(SysUser.class,userHealthQuestionDTO);
            sysUser.setUserId(userId);
            healthQuestionAnswerMapper.deleteHealthQuestionAnswerByCondition(Builder.of(HealthQuestionAnswer::new).with(HealthQuestionAnswer::setUserId, userId).build());
            if(userHealthQuestionDTO.getExerciseList().size() > 0){
                //运动
                List<HealthQuestionAnswer> exerciseAnswers = Convert.toList(HealthQuestionAnswer.class,userHealthQuestionDTO.getExerciseList());
                String questionAnswer = exercise(exerciseAnswers, ringHealthPlan, sysUser);
                //睡眠
                List<HealthQuestionAnswer> sleepAnswers = Convert.toList(HealthQuestionAnswer.class,userHealthQuestionDTO.getSleepList());
                sleep(sleepAnswers, ringHealthPlan);
                //饮食
                List<HealthQuestionAnswer> dietAnswers = Convert.toList(HealthQuestionAnswer.class,userHealthQuestionDTO.getDietList());
                diet(dietAnswers, ringHealthPlan,sysUser, questionAnswer);
                //情绪
                List<HealthQuestionAnswer> emotionAnswers = Convert.toList(HealthQuestionAnswer.class,userHealthQuestionDTO.getEmotionList());
                emotion(emotionAnswers, ringHealthPlan);
                //周期
                List<HealthQuestionAnswer> periodAnswers = Convert.toList(HealthQuestionAnswer.class,userHealthQuestionDTO.getPeriodList());
                period(emotionAnswers, ringHealthPlan);
                sysUserMapper.updateUser(sysUser);

                List<HealthQuestionAnswer> answers = new ArrayList<>();
                answers.addAll(exerciseAnswers);
                answers.addAll(sleepAnswers);
                answers.addAll(dietAnswers);
                answers.addAll(emotionAnswers);
                answers.addAll(periodAnswers);
                if(answers.size() > 0){
                    answers.forEach(answer ->{
                        answer.setUserId(userId);
                        answer.setCreateTime(new Date());
                        healthQuestionAnswerMapper.insertHealthQuestionAnswer(answer);
                    });
                }
            }else {
                ringHealthPlan.setPlanCycle(15);
                ringHealthPlan.setRestingHeartRate("60-100");
                ringHealthPlan.setBloodOxygenSaturation("95-100");
                ringHealthPlan.setHeartRateVariability("个人基线未形成");
                ringHealthPlan.setSleepQuality("良");
                ringHealthPlan.setEmotionManagement("25-60");
                ringHealthPlan.setStepCount(5000);
                ringHealthPlan.setExerciseDuration(30);
                ringHealthPlan.setExerciseCalorie(300);
                ringHealthPlan.setCalorie(Convert.toStr(150));
                String aiContent = "生成三个当日推荐事件返回XX（大于1000毫升）、XX（大于X分钟）、XX（大于X分钟），按照举例返回不超过8个字,例如：{\"shijian1\":\"xxx\",\"shijian2\":\"xxx\",\"shijian3\":\"xxx\"}，不要其他任何内容";
                String jsonStr = AiFactory.build(BizConstants.AI_PLATFORM.getValue()).chatCompletions(aiContent);
                Gson gson = new Gson();
                Map<String, Object> resultMap = gson.fromJson(jsonStr, Map.class);
                ringHealthPlan.setCheckInEvent(resultMap.get("shijian1")+","+ resultMap.get("shijian2")+","+ resultMap.get("shijian3"));
            }

            ringHealthPlan.setDeviceSn(userHealthQuestionDTO.getDeviceSn());
            ringHealthPlan.setPlanStatus(PlanStatusEnums.GENERATED.getCode());
            ringHealthPlan.setPlanName("健康问卷计划");
            ringHealthPlan.setUserId(userId);
            ringHealthPlan.setCreateTime(new Date());
            int result = ringHealthPlanMapper.insertRingHealthPlan(ringHealthPlan);
            return result;
        }catch (Exception e){
            log.error(e.getMessage());
            throw new ServiceException("健康问卷提交失败");
        }


    }

    @Override
    public UserHealthQuestionVO queryUserHealthQuestion() {
        long userId = SecurityUtils.getUserId();
        log.info("queryUserHealthQuestion: userId={}", userId);
        SysUser sysUser = sysUserMapper.queryUserHealthQuestion(userId);
        List<HealthQuestionAnswer> list = healthQuestionAnswerMapper.selectHealthQuestionAnswerList(Builder.of(HealthQuestionAnswer::new).with(HealthQuestionAnswer::setUserId, userId).build());
        UserHealthQuestionVO healthQuestionVO = Convert.convert(UserHealthQuestionVO.class,sysUser);
        healthQuestionVO.setQuestionAnswerVOList(Convert.toList(HealthQuestionAnswerVO.class,list));
        return healthQuestionVO;
    }

}
